package com.next

import grails.transaction.Transactional
import org.springframework.security.access.annotation.Secured

import static org.springframework.http.HttpStatus.*

@Secured(['ROLE_ADMINISTRATOR', 'ROLE_COMPANY_ADMINISTRATOR', 'ROLE_COMPANY_USER'])
@Transactional(readOnly = true)
class ContractController
{

    static allowedMethods = [save: "POST", update: "PUT", delete: "DELETE"]
    def springSecurityService
    def exportService

    def index(Integer max)
    {
        def username = springSecurityService?.getPrincipal()?.username
        def user = User.findByUsername(username)
        def contractList = []
        ArrayList count
        if (UserRole.findByUserAndRole(user, Role.findByAuthority("ROLE_ADMINISTRATOR")))
        {
            contractList = Contract.findAll("from Contract order by modifiedDate desc", [max: params.max ?: 10, offset: params.offset ?: 0])
            count = Contract.executeQuery("select count(id) from Contract")
        }
        else
        {
            contractList = Contract.findAll("from Contract where user.username = '${username}' order by modifiedDate desc", [max: params.max ?: 10, offset: params.offset ?: 0])
            count = Contract.executeQuery("select count(id) from Contract where user.username = '${username}'")
        }

        respond contractList, model: [contractCount: count[0], params: params]

    }

    def show(Contract contract)
    {
        def addressList = Address.findAll("from Address where contract.id = ?", [contract.id])
        def attachmentList = Attachment.findAll("from Attachment where contract.id = ?", [contract.id])
        def flexFieldInstanceList = FlexFieldInstance.findAll("from FlexFieldInstance where contract.id = ?", [contract.id])
        def opportunityContractList = OpportunityContract.findAll("from OpportunityContract where contract.id = ? order by createdDate desc", [contract.id])
        def assetList = Asset.findAll("from Asset where contract.id = ? order by createdDate desc", [contract.id])

        respond contract, model: [addressList: addressList, attachmentList: attachmentList, flexFieldInstanceList: flexFieldInstanceList, opportunityContractList: opportunityContractList, assetList: assetList]
    }

    def create()
    {
        def username = springSecurityService?.getPrincipal()?.username
        def user = User.findByUsername(username)
        respond new Contract(params), model: [user: user]
    }

    @Transactional
    def save(Contract contract)
    {
        def username = springSecurityService?.getPrincipal()?.username
        def user = User.findByUsername(username)

        if (contract == null)
        {
            transactionStatus.setRollbackOnly()
            notFound()
            return
        }

        if (contract.hasErrors())
        {
            transactionStatus.setRollbackOnly()
            respond contract.errors, model: [user: user], view: 'create'
            return
        }

        contract.save flush: true

        request.withFormat {
            form multipartForm {
                flash.message = message(code: 'default.created.message', args: [message(code: 'contract.label', default: 'Contract'), contract.id])
                redirect contract
            }
            '*' { respond contract, [status: CREATED] }
        }
    }

    def edit(Contract contract)
    {
        def username = springSecurityService?.getPrincipal()?.username
        def user = User.findByUsername(username)
        respond contract, model: [user: user]
    }

    @Transactional
    def update(Contract contract)
    {
        def username = springSecurityService?.getPrincipal()?.username
        def user = User.findByUsername(username)

        if (contract == null)
        {
            transactionStatus.setRollbackOnly()
            notFound()
            return
        }

        if (contract.hasErrors())
        {
            transactionStatus.setRollbackOnly()
            respond contract.errors, model: [user: user], view: 'edit'
            return
        }

        contract.save flush: true

        request.withFormat {
            form multipartForm {
                flash.message = message(code: 'default.updated.message', args: [message(code: 'contract.label', default: 'Contract'), contract.id])
                redirect contract
            }
            '*' { respond contract, [status: OK] }
        }
    }

    @Transactional
    def delete(Contract contract)
    {
        if (contract == null)
        {
            transactionStatus.setRollbackOnly()
            notFound()
            return
        }

        contract.delete flush: true

        request.withFormat {
            form multipartForm {
                flash.message = message(code: 'default.deleted.message', args: [message(code: 'contract.label', default: 'Contract'), contract.id])
                redirect action: "index", method: "GET"
            }
            '*' { render status: NO_CONTENT }
        }
    }

    protected void notFound()
    {
        request.withFormat {
            form multipartForm {
                flash.message = message(code: 'default.not.found.message', args: [message(code: 'contract.label', default: 'Contract'), params.id])
                redirect action: "index", method: "GET"
            }
            '*' { render status: NOT_FOUND }
        }
    }

    def searchContract()
    {
        def username = springSecurityService?.getPrincipal()?.username
        String serialNumber = params["serialNumber"]

        String sql = "from Contract where user.username = '${username}'"
        if (serialNumber)
        {
            sql += " and serialNumber like '%${serialNumber}%'"
        }
        String countSql = "select count(id) " + sql
        sql += " order by modifiedDate desc"

        def list = Contract.findAll(sql, [max: params.max ?: 10, offset: params.offset ?: 0])
        def count = Contract.executeQuery(countSql)

        respond list, model: [contractCount: count[0], params: params], view: 'index'
    }

    def exportContract()
    {
        def username = springSecurityService?.getPrincipal()?.username
        String serialNumber = params["serialNumber"]

        String sql = "from Contract where user.username = '${username}'"
        if (serialNumber)
        {
            sql += " and serialNumber like '%${serialNumber}%'"
        }
        String countSql = "select count(id) " + sql
        sql += " order by modifiedDate desc"

        def list = Contract.findAll(sql)
        def count = Contract.executeQuery(countSql)

        if (params?.f && params.f != "html")
        {
            response.contentType = grailsApplication.config.grails.mime.types[params.f]
            response.setHeader("Content-disposition", "attachment; filename=contract.${params.extension}")
            List fields = ["serialNumber", "subject", "type.name", "status.name", "account.name", "user.fullName", "startTime", "endTime", "createdDate", "modifiedDate"]
            Map labels = ["serialNumber": "合同编号", "subject": "标题", "type.name": "合同类型", "status.name": "状态", "account.name": "客户", "user.fullName": "销售人员姓名", "startTime": "开始时间", "endTime": "结束时间", "createdDate": "创建时间", "modifiedDate": "修改时间"]
            exportService.export(params.f, response.outputStream, list, fields, labels, [:], [:])
        }
    }
}
